package study.lagou.com.config;

import com.mchange.v2.c3p0.ComboPooledDataSource;
import org.dom4j.Document;
import org.dom4j.DocumentException;
import org.dom4j.Element;
import org.dom4j.io.SAXReader;
import study.lagou.com.io.Resources;
import study.lagou.com.pojo.Configuration;

import java.beans.PropertyVetoException;
import java.io.InputStream;
import java.util.List;
import java.util.Properties;

/**
 * @Description: 功能描述
 * @Author houjh
 * @Email: happyxiaohou@gmail.com
 * @Date: 2021-1-28 22:56
 */
public class XMLConfigBuilder {

    private Configuration configuration;

    public XMLConfigBuilder() {
        this.configuration = new Configuration();
    }

    /**
     * 该方法就是使用dom4j对配置文件进行解析，然后将配置文件信息封装到Configuration类中
     * @param inputStream
     * @return
     * @throws DocumentException
     */
    public Configuration parseConfig(InputStream inputStream) throws DocumentException, PropertyVetoException {
        //通过dom4j包中的SAXReader类对读取出来字节输入流进行解析
        Document document = new SAXReader().read(inputStream);
        Element rootElement = document.getRootElement();
        //通过//这种表示方法，不论property属性在xml文件中的哪一些都可以直接读取到,通过rootElement.selectNodes方法
        //可以获取到对应配置文件中属性为property的所有Element
        List<Element> list = rootElement.selectNodes("//property");
        //这里我们定义一个Properties对象来存储配置文件中读取出来的元素，可以存储key和value的对象还可以是Map，但是我们
        //这里使用Properties来存储，因为后面创建数据库连接池会使用到
        Properties properties = new Properties();
        for (Element element : list) {
            String name = element.attributeValue("name");
            String value = element.attributeValue("value");
            properties.put(name,value);
        }

        //创建数据库连接池对象
        ComboPooledDataSource comboPooledDataSource = new ComboPooledDataSource();
        comboPooledDataSource.setDriverClass(properties.getProperty("driverClass"));
        comboPooledDataSource.setJdbcUrl(properties.getProperty("jdbcUrl"));
        comboPooledDataSource.setUser(properties.getProperty("username"));
        comboPooledDataSource.setPassword(properties.getProperty("password"));

        //设置Configuration对象中的DataSource属性
        configuration.setDataSource(comboPooledDataSource);

        //解析mapper.xml文件,首先获取到路径，然后通过路径将配置文件加载成字节输入流再用dom4j进行解析
        List<Element> mapperList = rootElement.selectNodes("//mapper");
        for (Element element : mapperList) {
            String mapperPath = element.attributeValue("resource");
            XMLMapperBuilder xmlMapperBuilder = new XMLMapperBuilder(configuration);
            InputStream resourceAsStream = Resources.getResourceAsStream(mapperPath);
            xmlMapperBuilder.parse(resourceAsStream);
        }

        return configuration;
    }
}
